#ifndef PROXY_CONN_TCPSACCPETERVER_H_
#define PROXY_CONN_TCPSACCPETERVER_H_

#include "proxy/base/proxybase.h"

namespace proxy{

  class TcpAccpetServer : public boost::noncopyable,
    public boost::enable_shared_from_this < TcpAccpetServer > {
  public:
    // Base defines
    typedef boost::shared_ptr<TcpAccpetServer> Ptr;
    typedef boost::function<void(TcpAccpetServer::Ptr accpet_server,
      socket_ptr connect)> SignalNewConnectCallback;
    typedef boost::function < void(TcpAccpetServer::Ptr accpet_server,
      const boost::system::error_code& err) > SignalAcceptErrorCallback;

    TcpAccpetServer(
      ios_deque& io_services, boost::asio::io_service& accpet_service,
      std::string addr, uint16 port);
    virtual ~TcpAccpetServer();

    void SetSignalNewConnect(SignalNewConnectCallback callback){
      SignalNewConnect = callback;
    }
    void SetSignalAcceptError(SignalAcceptErrorCallback callback){
      SignalAcceptError = callback;
    }

    // Thread safe
    bool Start();
    // Thread safe
    void Stop();
    // Help function
    const boost::asio::ip::tcp::endpoint& bind_addr() const{
      return bind_addr_;
    }
  private:
    void HandleStartAcceptor();
    void HandleStopTcpServer();
    void HandleAcceptor(socket_ptr connect, const boost::system::error_code& err);
    boost::asio::io_service& get_best_io_server();
  private:
    SignalNewConnectCallback SignalNewConnect;
    SignalAcceptErrorCallback SignalAcceptError;
    boost::asio::io_service& accpet_service_;
    ios_deque& io_services_;
    boost::asio::ip::tcp::endpoint bind_addr_;
    boost::scoped_ptr<boost::asio::ip::tcp::acceptor> acceptor_;
    bool stop_;
  };
} // namespace proxy

#endif // PROXY_CONN_TCPSACCPETERVER_H_